% Written by Samuel Hurtado



function G4_new = unfoldg4(G4,n)

% This function is designed to "unfold" matrix g_3 generated in the third
% order approximation of a policy function in Dynare.
% Arguments:
% G3 => matrix g_3, normally stored at oo_.dr.g_3, after the computation of
% a third-order approximation;
% n => number of state variables + shocks in the model (easy: n=size(G1,2))



% replicate the order in which Dynare stored these numbers, leave zero on the elements that were discarded

G4_index=zeros(n,n,n,n);

mycounter=0;
totalcounter = size(G4,2);
for x=1:n
    for y=x:n
        for z=y:n
            for zz = z:n
                mycounter=mycounter+1;
                tracker = mycounter/totalcounter*100;
                %disp(['tracker ' num2str(tracker) '%']);
                G4_index(x,y,z,zz)=mycounter;
            end
        end
    end
end



% populate G3_new, pulling out of G3 the elements designated by G4_index
% (when choosing elements of G4_index, sort index to avoid all the elements that were discarded)

G4_new = zeros(size(G4,1),n^4);

mycounter=0;
totalcounter = n*n*n*n;
for x=1:n
    for y=1:n
        for z=1:n
            for zz=1:n
                mycounter = mycounter+1;
                tracker = mycounter/totalcounter*100;
                %disp(['tracker ' num2str(tracker) '%'])
                xyz=sort([x y z zz]);
                G4_new(:,mycounter)=G4(:,G4_index(xyz(1),xyz(2),xyz(3),xyz(4)));
            end
        end
    end
end
